import React, { Component } from 'react'

export default class HelloWorld extends Component {
  // 挂载阶段： constructor(): 创建实例对象组件 -> render(): 生成虚拟DOM -> 虚拟DOM转换为真实DOM元素 -> 执行componentDidMount()钩子
  // 1. 构造方法
  // 作用：1.初始化state状态，2.为时间绑定this
  constructor() {
    console.log('constructor')
    super()
    this.state = {
      message: 'hello world',
    }
  }

  // 更新阶段：修改props，修改state数据，forceUpdate -> componentDidUpdate
  /*
    具体：
     shouldComponentUpdate：是否执行render函数(第一次执行更新执行，后续不在执行) 
        -> render -> getSnapshotBeforeUpdate: 保持上一次相关数据 -> componentDidUpdate
  */
  btnClick() {
    this.setState({
      message: 'hello react',
    })
  }

  // 2.执行render方法
  render() {
    const { message } = this.state
    console.log('render')

    return (
      <div>
        <p>{message}是程序员第一个代码！</p>
        <button onClick={() => this.btnClick()}>修改message文本</button>
      </div>
    )
  }

  // 3.组件被挂在到DOM
  // 作用：1.依赖DOM操作可以在这里进行，2.发送网络请求，3.添加订阅（会在componentWillUnmount取消订阅）
  componentDidMount() {
    console.log('componentDidMount')
  }

  // 4.组件DDM被更新完成
  // 作用：1.组件更新后，对DOM进行操作，2.更新前后props进行比较，重新发送网络请求（props未发生变化，则不会发送网络请求）
  componentDidUpdate(prevProps, prevState, snapshoot) {
    console.log('componentDidUpdate', prevProps, prevState, snapshoot)
  }

  // 5.组件将要协助
  // 卸载阶段：componentWillUnmount
  // 作用：1.清楚定时器 2.取消订阅
  componentWillUnmount() {
    console.log('componentWillUnmount')
  }

  // 不常用的生命周期
  // 作用：在更新DOM之前（render），会先执行这个函数，如果返回false，则不更新DOM（不执行render）
  shouldComponentUpdate() {
    console.log('shouldComponentUpdate')
    return true
  }

  // 快照：确定更新DOM后，还会执行这个函数
  // 作用：将更新之前的数据进行保持, 数据会传入给componentDidUpdate中
  getSnapshotBeforeUpdate() {
    console.log('getSnapshotBeforeUpdate')
    return {
      useScroll: 100,
    }
  }
}
